package com.canyou.api;

import com.canyou.constants.MsgConstants;
import com.canyou.enums.ErrorCodeEnum;
import com.canyou.utils.StringUtils;
import com.fasterxml.jackson.annotation.JsonInclude;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import lombok.NoArgsConstructor;
import lombok.experimental.Accessors;

import java.io.Serializable;

/**
 * api返回响应结果
 *
 * @author cgz
 * @date 2018-12-06
 */
@NoArgsConstructor
@Data
@Accessors(chain = true)
@JsonInclude(JsonInclude.Include.NON_NULL)
@ApiModel(description = "返回接口值实体")
public class ResponseBO<T> implements IErrorCode, Serializable {

    private static final long serialVersionUID = -8713837118340960775L;

    /**
     * 返回状态Code
     */
    @ApiModelProperty(value = "返回状态Code", example = "2000")
    private Integer code;

    /**
     * 返回值说明
     */
    @ApiModelProperty(value = "返回值说明")
    private String msg;

    /**
     * 返回结果
     */
    @ApiModelProperty(value = "返回结果")
    private T data;

    private ResponseBO(Integer code, String msg, T data) {
        super();
        this.code = code;
        this.msg = msg;
        this.data = data;
    }

    private ResponseBO(Integer code, String msg) {
        this(code, msg, null);
    }

    private ResponseBO(IErrorCode errorCode) {
        this(errorCode.getCode(), errorCode.getMsg());
    }

    private ResponseBO(IErrorCode errorCode, T data) {
        this(errorCode.getCode(), errorCode.getMsg(), data);
    }

    private static ResponseBO rest(Integer code, String msg) {
        return rest(code, msg, null);
    }

    private static <T> ResponseBO<T> rest(Integer code, String msg, T data) {
        return new ResponseBO<>(code, msg, data);
    }

    public static ResponseBO ok() {
        return new ResponseBO(ErrorCodeEnum.SUCCESS);
    }

    public static ResponseBO ok(String msg) {
        return new ResponseBO<>(ErrorCodeEnum.SUCCESS.getCode(), msg);
    }

    public static <T> ResponseBO<T> ok(T data) {
        return new ResponseBO<>(ErrorCodeEnum.SUCCESS, data);
    }

    public static <T> ResponseBO<T> ok(T data, String msg) {
        return new ResponseBO<>(ErrorCodeEnum.SUCCESS.getCode(), msg, data);
    }

    public static ResponseBO error(IErrorCode errorCode) {
        return error(errorCode, errorCode.getMsg());
    }

    public static ResponseBO error(IErrorCode errorCode, String extMsg) {
        return rest(errorCode.getCode(), extMsg);
    }

    /**
     * 系统故障
     *
     * @return
     */
    public static ResponseBO error() {
        return error(ErrorCodeEnum.FAIL);
    }

    /**
     * invalid_token 无效
     *
     * @return
     */
    public static ResponseBO invalidAccessToken() {
        return error(ErrorCodeEnum.INVALID_ACCESS_TOKEN);
    }

    /**
     * refresh_token无效
     *
     * @return
     */
    public static ResponseBO invalidRefreshToken() {
        return error(ErrorCodeEnum.INVALID_REFRESH_TOKEN);
    }

    /**
     * 用户未授权执行操作
     *
     * @return
     */
    public static ResponseBO unAuthorized() {
        return error(ErrorCodeEnum.UNAUTHORIZED);
    }

    /**
     * 数据非法
     *
     * @param msg
     * @return
     */
    public static ResponseBO illegal(String msg) {
        return error(ErrorCodeEnum.ILLEGAL, msg);
    }

    /**
     * 操作失败，可能存在异常
     *
     * @param msg
     * @return
     */
    public static ResponseBO fail(String msg) {
        return error(ErrorCodeEnum.FAIL, StringUtils.isNotBlank(msg) ? msg : ErrorCodeEnum.FAIL.getMsg());
    }

    /**
     * 自定义错误码
     *
     * @param msg
     * @return
     */
    public static ResponseBO fail(Integer code, String msg) {
        return rest(code, msg);
    }

    /**
     * 重复提交
     *
     * @param msg
     * @return
     */
    public static ResponseBO repeatSubmit(String msg) {
        return error(ErrorCodeEnum.REPEAT_SUBMIT, msg);
    }

    /**
     * 保存结果提示语处理
     *
     * @param isSuccess
     * @param id
     * @return
     */
    public static ResponseBO result(boolean isSuccess, Long id) {
        if (isSuccess) {
            if (id != null) {
                return ResponseBO.ok(true, MsgConstants.EDIT_SUCCESS);
            } else {
                return ResponseBO.ok(true, MsgConstants.ADD_SUCCESS);
            }
        } else {
            if (id != null) {
                return ResponseBO.illegal(ErrorCodeEnum.VERSION_ERROR.getMsg());
            } else {
                return ResponseBO.illegal(MsgConstants.ADD_FAIL);
            }
        }
    }
}
